package es.uma.scgt.controlador;

import java.sql.Timestamp;
import java.text.MessageFormat;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Locale;

import javax.swing.JOptionPane;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.stereotype.Controller;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.ui.ModelMap;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;

import es.uma.scgt.autenticacion.UserDetailsImpl;
import es.uma.scgt.dao.EquipoDao;
import es.uma.scgt.dao.PeticionDao;
import es.uma.scgt.dao.UsuarioDao;
import es.uma.scgt.mail.Correo;
import es.uma.scgt.modelo.Equipo;
import es.uma.scgt.modelo.FaseP;
import es.uma.scgt.modelo.Peticion;
import es.uma.scgt.modelo.Usuario;

@Controller
public class PeticionControlador{
	
private static final String PAGINA_CRUD_PETICION = "CrudPeticion";
private static final String PAGINA_CRUD_PETICIONESTADO = "CrudPeticionEstado";
private static final String PARAM_EQUIPO_LIST = "equipoList";
private static final String PARAM_BORRADORES_LIST = "borradoresList";
private static final String PARAM_ENVIADAS_LIST = "enviadasList";
private static final String PARAM_ENPROCESO_LIST = "enProcesoList";
private static final String PARAM_FINALIZADAS_LIST = "finalizadasList";
private static final String PARAM_PETICION = "peticion";
private static final String PARAM_PETICIONESDEEQUIPO = "PdeEquipoList";

@Autowired
private EquipoDao equipoDao;
@Autowired
private UsuarioDao usuarioDao;
@Autowired
private PeticionDao peticionDao;

//Cuando llama a la p�gina Petici�n desde el men�, la primera que se ve	
	
	@RequestMapping("/CrudPeticion")
	@Transactional
	public String iniCrudPeticion(ModelMap model, @RequestParam(required=false,value="pid")Integer peticionId) {
		
		model.addAttribute(PARAM_EQUIPO_LIST, equipoDao.getTodosEquipo());
		model.addAttribute(PARAM_BORRADORES_LIST, peticionDao.getBorradores());
		return PAGINA_CRUD_PETICION;
	}
	
	@RequestMapping("/CrudPeticionDesdeEstado")
	@Transactional
	public String iniCrudPeticionDesdeEstado(ModelMap model, @RequestParam(required=false,value="pid")Integer peticionId) {
		
		model.addAttribute(PARAM_EQUIPO_LIST, equipoDao.getTodosEquipo());
		model.addAttribute(PARAM_BORRADORES_LIST, peticionDao.getBorradores());
		if (peticionId != null){
			model.addAttribute(PARAM_PETICION, peticionDao.encuentraPeticionPorId(peticionId));
			
		}
		return PAGINA_CRUD_PETICION;
	}
	
	
	
	@RequestMapping("/CrudPeticionEstado")
	@Transactional
	public String iniCrudPeticionEstado(ModelMap model) {
		
		model.addAttribute(PARAM_ENVIADAS_LIST, peticionDao.getEnviadas());
		List<Peticion> enProceso = peticionDao.getEnProceso();
		model.addAttribute(PARAM_ENPROCESO_LIST, enProceso);
		model.addAttribute(PARAM_FINALIZADAS_LIST, peticionDao.getFinalizadas());
		
		UserDetailsImpl userDetails = (UserDetailsImpl) SecurityContextHolder.getContext().getAuthentication().getPrincipal(); 
		List<Equipo> listaEquipos = userDetails.getListaEquipos();
		
		List<Peticion> litapeticiones=peticionDao.pEquiposxUsuario(listaEquipos);
		model.addAttribute(PARAM_PETICIONESDEEQUIPO,litapeticiones);
		return PAGINA_CRUD_PETICIONESTADO;
		
	}
	
	//Click Guardar Borrador
	public String guardarPetBorrador(ModelMap model, @RequestParam("peticionid") Integer peticionId, @RequestParam("asunto") String asunto, @RequestParam("descripcion") String descripcion, @RequestParam("emisor") String emisor, @RequestParam("receptor") Integer receptor, @RequestParam("fEntrega") Date fCreacion, @RequestParam("fEntrega") Date fEntrega){
		Peticion tmpPeticion = null;
		String descripcion2;
		descripcion2 = descripcion.replace("\r\n", "\\r\\n");
		if (peticionId == null){ // Esto lo pongo por si luego puedo utilizar esta funci�n para hacer el modificar tb, ahora siempre va a ser nulo
			//Nueva Peticion fase Borrador
				tmpPeticion = new Peticion();
				rellenarPeticion(peticionId, asunto,descripcion2, emisor, receptor, fCreacion, fEntrega,tmpPeticion);
				peticionDao.peticionBorrador(tmpPeticion);
			
		}else{// Modificar Petici�n
			tmpPeticion = peticionDao.encuentraPeticionPorId(peticionId);
			rellenarPeticion(peticionId, asunto,descripcion2, emisor, receptor, fCreacion, fEntrega,tmpPeticion);
			peticionDao.peticionBorrador(tmpPeticion);
		}
		
		
		model.addAttribute(PARAM_EQUIPO_LIST, equipoDao.listaEquipo());
		model.addAttribute(PARAM_BORRADORES_LIST, peticionDao.getBorradores());
		return PAGINA_CRUD_PETICION;
	}
	
	//Click Enviar
	public String enviarPeticion(ModelMap model, @RequestParam("peticionid") Integer peticionId, @RequestParam("asunto") String asunto, @RequestParam("descripcion") String descripcion, @RequestParam("emisor") String emisor, @RequestParam("receptor") Integer receptor, @RequestParam("fCreacion") Date fCreacion, @RequestParam("fEntrega") Date fEntrega){
		boolean esNuevo = false;
		Peticion tmpPeticion;
		String descripcion2;
		descripcion2 = descripcion.replace("\r\n", "\\r\\n");
		if (peticionId == null){ // Esto lo pongo por si luego puedo utilizar esta funci�n para hacer el modificar tb, ahora siempre va a ser nulo
			tmpPeticion = new Peticion();
			rellenarPeticion(peticionId, asunto,descripcion2, emisor, receptor, fCreacion, fEntrega,tmpPeticion);
			tmpPeticion.setFase(FaseP.E);
			peticionDao.peticionEnviar(tmpPeticion);	
			esNuevo = true;//Se crea la peticion
		}else{ //Modificar Peticion
			tmpPeticion = peticionDao.encuentraPeticionPorId(peticionId);
			//Si viene de borradores tb se envia por primera vez aunque la peticion se haya creado antes
			if (tmpPeticion.getFase()==FaseP.B){
				tmpPeticion.setFase(FaseP.E);
				esNuevo = true;
			}
			rellenarPeticion(peticionId, asunto,descripcion2, emisor, receptor, fCreacion, fEntrega,tmpPeticion);
			peticionDao.peticionEnviar(tmpPeticion);
		} 
		
		
		//Sea la peticion nueva o no enviamos el correo igualmente
		//Constructor Correo
		Correo c = new Correo();
		Equipo equipoReceptor = equipoDao.getEquipoPorId(receptor);
		List<Usuario> usuariosReceptores = equipoReceptor.getUsuarios();
		List<String> emails = new ArrayList<String>();
		for (Usuario usuario : usuariosReceptores) {
			emails.add(usuario.getEmail());
		}
		String cabecera, subject, body, cuerpo;
		Date fechaEntrega = tmpPeticion.getFechaEntrega();
		String NombreEmisor = tmpPeticion.getEmisor().getNombre();
		String ApellidoEmisor = tmpPeticion.getEmisor().getApellido1();
		
		//Fase es Enviado y es nuevo, se envia por primera vez
		if ((tmpPeticion.getFase()==FaseP.E) && (esNuevo)){
			 cabecera = "Nueva Petici�n: {0}";
			 subject = MessageFormat.format(cabecera, asunto);
			 
			 cuerpo = "<b>Se necesita:</b> <br> <br> {0} <br><br>  <b>Debe de ser entregado antes del:</b> {1}. <br> <br> <i>Atentamente:</i> {2} {3}.";
			 body = MessageFormat.format(cuerpo, descripcion,fechaEntrega, NombreEmisor,ApellidoEmisor);
			 
		}else if ((tmpPeticion.getFase()==FaseP.E)&& (!esNuevo)){
			 cabecera = "Modificar Petici�n: {0}. Asunto:{1}";
			 subject = MessageFormat.format(cabecera, peticionId ,asunto);
			 
			 cuerpo = "<b>Se necesita (actualizada)</b>: {0} <br><br>  Debe de ser entregado antes del: {1}. <br><br> <i>Atentamente:</i> {2} {3}.";
			 body = MessageFormat.format(cuerpo, descripcion,fechaEntrega, NombreEmisor,ApellidoEmisor);
			 
		}else{ //La fase tiene que ser en Proceso
			 cabecera = "Modificar Petici�n en Proceso: {0}. Asunto:{1}";
			 subject = MessageFormat.format(cabecera, peticionId ,asunto);
			 
			 cuerpo = "<b>A/A</b> desarrolladores de la peticion: {0}. <br><br> La petici�n se actualiza de la seguiente forma:{1}. <br><br> Debe de ser entregado antes del: {2}. <br><br> Disculpen las molestias. <br><br> <i>Atentamente:</i> {3} {4}";
			 body = MessageFormat.format(cuerpo, peticionId,descripcion,fechaEntrega, NombreEmisor,ApellidoEmisor);
			 
		}
		
		JOptionPane.showMessageDialog(null, "Peticion enviada. Para cualquier duda consulte con el departamento receptor.");
		//Accion EnviarCorreo
		c.enviarCorreo(emails, subject, body);
		
		model.addAttribute(PARAM_EQUIPO_LIST, equipoDao.listaEquipo());
		model.addAttribute(PARAM_BORRADORES_LIST, peticionDao.getBorradores());
		
		return PAGINA_CRUD_PETICION;
		
	}
	
	
	@RequestMapping("/SubmitPeticion")
	@Transactional
	public String submitPeticion (ModelMap model,@RequestParam("tipo") String tipo, @RequestParam(value="peticionid", required=false) Integer peticionId, @RequestParam("asunto") String asunto, @RequestParam("descripcion") String descripcion, @RequestParam("emisor") String emisor, @RequestParam("receptor") Integer receptor, @RequestParam("fCreacion") String fCreacion, @RequestParam("fEntrega") String fEntrega){
		Date fCreacionDate = convierteStringAFecha(fCreacion);
		Date fEntregaDate = convierteStringAFecha(fEntrega);
		if ("borrador".equalsIgnoreCase(tipo)){
			//FaseP fase = FaseP.B;
			
			return  guardarPetBorrador(model, peticionId, asunto, descripcion, emisor, receptor, fCreacionDate, fEntregaDate);
			//Poner mensaje de Borrador enviado con exito
		}else{
			//enviar
			return enviarPeticion(model, peticionId, asunto, descripcion, emisor, receptor, fCreacionDate, fEntregaDate);
		}	
	}
	
	private Date convierteStringAFecha(String string) {
		Date date = new Date();
		try {
			 date = new SimpleDateFormat("dd/MM/yyyy", Locale.FRANCE).parse(string);
		} catch (ParseException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		return date;
	}

	
	private void rellenarPeticion(Integer peticionId, String asunto,
			String descripcion, String emisor, Integer receptor, Date fCreacion,
			Date fEntrega, Peticion peticion) {
		
		//TODO
		
		List<Usuario> emisore = new ArrayList<Usuario>();
		
		peticion.setId(peticionId);
		peticion.setTitulo(asunto);
		
		emisore = usuarioDao.usuarioPorEmail(emisor);
		peticion.setEmisor(emisore.get(0));
		
		peticion.setReceptor(equipoDao.getEquipoPorId(receptor));
		peticion.setDescripcion(descripcion);
		peticion.setFechaEnvio(new Timestamp(fCreacion.getTime()));
		peticion.setFechaEntrega(new Timestamp(fEntrega.getTime()));
		
	}
	
	@RequestMapping("/SubmitEditarBorrarPeticion")
	@Transactional
	public String submitEditarBorrarPeticion (ModelMap model, @RequestParam("tipo2") String tipo2,@RequestParam(value="idEliminar", required=true) Integer idEliminar){
		try{
			if ("eliminar".equals(tipo2)){
				peticionDao.BorrarPeticion(idEliminar);
			}
		}catch (Exception e) {
			// error al borrar, pasalo en el modelo y lo ensenas en un alert si hace falta
			model.addAttribute("alertMensaje", "Imposible borrar la peticion "+ idEliminar);
		}
		
		model.addAttribute(PARAM_EQUIPO_LIST, equipoDao.getTodosEquipo());
		model.addAttribute(PARAM_BORRADORES_LIST, peticionDao.getBorradores());
		return PAGINA_CRUD_PETICION;
		
	}
	
	
}